package cn.vcjf.weapp.api.goods.service.impl;

import cn.vcjf.weapp.api.goods.entity.GoodsOrder;
import cn.vcjf.weapp.api.goods.entity.GoodsOrderItem;
import cn.vcjf.weapp.api.goods.entity.GoodsRefundOrder;
import cn.vcjf.weapp.api.goods.mapper.GoodsOrderItemMapper;
import cn.vcjf.weapp.api.goods.mapper.GoodsOrderMapper;
import cn.vcjf.weapp.api.goods.mapper.GoodsRefundOrderMapper;
import cn.vcjf.weapp.api.goods.service.GoodsRefundOrderService;
import cn.vcjf.weapp.api.payment.qfwxpay.model.VcQfPayRes;
import cn.vcjf.weapp.api.payment.qfwxpay.service.AbstractQfRefundService;
import cn.vcjf.weapp.api.payment.qfwxpay.service.AbstractQfWxPayAuth;
import cn.vcjf.weapp.api.setting.entity.OrderOptionConfig;
import cn.vcjf.weapp.api.user.service.UserService;
import cn.vcjf.weapp.common.exception.ServiceException;
import cn.vcjf.weapp.common.util.CacheUtils;
import cn.vcjf.weapp.common.util.DateUtils;
import cn.vcjf.weapp.common.util.ThreadManager;
import cn.vcjf.weapp.common.util.weixin.WechatUtils;
import cn.vcjf.weapp.common.web.TableResult;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.plugins.Page;
import com.baomidou.mybatisplus.service.impl.ServiceImpl;
import org.apache.commons.lang3.StringUtils;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Queue;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author zhengzihang
 * @since 2018-09-25
 */
@Service("goodsRefundOrderService")
public class GoodsRefundOrderServiceImpl extends ServiceImpl<GoodsRefundOrderMapper, GoodsRefundOrder> implements GoodsRefundOrderService {

	private Logger logger = LogManager.getLogger(GoodsRefundOrderServiceImpl.class);

	@Resource
	private GoodsOrderItemMapper goodsOrderItemMapper;
	@Resource
	private GoodsOrderMapper goodsOrderMapper;
	@Resource
	OrderOptionConfig orderOptionConfig;
	@Resource
	private AbstractQfWxPayAuth abstractQfWxPayAuth;
	@Resource
	public AbstractQfRefundService qianFangRefundApi;
	@Resource
	public UserService userService;

	/**
	 * 订单退款参数校验
	 * @param goodsRefundOrder
	 */
	public void checkRefundOrder(GoodsRefundOrder goodsRefundOrder){
		if(goodsRefundOrder == null){
			throw new ServiceException("无退款信息");
		}
		if(goodsRefundOrder.getOrderNo() == null){
			throw new ServiceException("退款订单号不能为空");
		}
		GoodsOrder order = new GoodsOrder();
		order.setOrderNo(goodsRefundOrder.getOrderNo());
		GoodsOrder goodsOrder = goodsOrderMapper.selectOne(order);
		//订单退款,售后时间校验
		if (goodsOrder.getStatus() == 4 && goodsOrder.getCreateTime().getTime()-System.currentTimeMillis()>1000L*60*60*24* orderOptionConfig.expireDays){
			throw new ServiceException("订单已完成超过"+ orderOptionConfig.expireDays+"天");
		}
		if(goodsOrder.getStatus() != 2 && goodsOrder.getStatus() != 3){
			throw new ServiceException("支付订单状态异常");
		}
		if(goodsRefundOrder.getOrderType() == null){
			throw new ServiceException("退款订单类型不能为空");
		}
		if(goodsRefundOrder.getOrderItems() == null||goodsRefundOrder.getOrderItems().isEmpty()){
			throw new ServiceException("退款订单的商品不能为空");
		}
		if(goodsRefundOrder.getRefundMoney() == null){
			throw new ServiceException("退款金额不能为空");
		}
		if(goodsRefundOrder.getRefundType() == null){
			throw new ServiceException("退款类型不能为空");
		}
		if(goodsRefundOrder.getReason() == null){
			throw new ServiceException("退款原因不能为空");
		}
		if(goodsRefundOrder.getReasonDes() == null){
			throw new ServiceException("退款问题描述不能为空");
		}
		//(1,正常,2,退换,3,仅退款,4,退款退货)
		if(goodsRefundOrder.getRefundType() == 4){
			if (StringUtils.isBlank(goodsRefundOrder.getGoodsFileId1())
			&&StringUtils.isBlank(goodsRefundOrder.getGoodsFileId2())
			&&StringUtils.isBlank(goodsRefundOrder.getGoodsFileId3()) ){
				throw new ServiceException("退款商品图片或凭证不能为空");
			}
		}
		if(goodsRefundOrder.getUserId() == null){
			throw new ServiceException("退款用户id不能为空");
		}

	}
	/**
	 * 发起订单退款
	 *
	 * @param goodsRefundOrder
	 * @return
	 */
	@Override
	@Transactional
	public TableResult refundGoodsOrder(GoodsRefundOrder goodsRefundOrder) {

		goodsRefundOrder = baseMapper.selectById(goodsRefundOrder.getId());

		//参数校验
		checkRefundOrder(goodsRefundOrder);

		//(1,正常,2,退换,3,仅退款,4,退款退货)
		Integer refundType = goodsRefundOrder.getRefundType();
		//
		String orderNo = goodsRefundOrder.getOrderNo();
		//订单类型(1,普通,2,拼团,3,砍价,4套餐)
		if (goodsRefundOrder.getOrderType() == null) {
			return TableResult.ErrorResult("订单类型不能为空");
		}
		//保存退款订单
		goodsRefundOrder.preInsert();
		boolean b = this.insert(goodsRefundOrder);
		if (!b){
			throw new ServiceException("发起订单退款失败");
		}

		List<GoodsOrderItem> orderItems = null;
		orderItems = goodsRefundOrder.getOrderItems();

		//订单类型(1,普通,2,拼团,3,砍价,4套餐)
		if (goodsRefundOrder.getOrderType() == 1) {
		} else if (goodsRefundOrder.getOrderType() == 4) {

		} else {

		}
		BigDecimal refundMoney = goodsRefundOrder.getRefundMoney();
		BigDecimal money = new BigDecimal(0);

		//记录退款的具体商品
		for (GoodsOrderItem item : orderItems) {
			item.setRefundOrderId(goodsRefundOrder.getId());
			item.setStatus(refundType);
			money = money.add(item.getGoodsPrice().multiply(new BigDecimal(item.getGoodsNum())));
			goodsOrderItemMapper.updateById(item);
		}
		//普通订单,校验退款金额
		if (goodsRefundOrder.getOrderType() == 1) {
			if (money.compareTo(refundMoney) < 0) {
				throw new ServiceException("退款金额不正确");
			}
		} else {
//			goodsRefundOrder.setRefundMoney();
		}

		GoodsOrder goodsOrder = new GoodsOrder();
		goodsOrder.setOrderNo(orderNo);
		GoodsOrder updateOrder = goodsOrderMapper.selectOne(goodsOrder);
		BigDecimal traActualMoney = updateOrder.getTraActualMoney();
		if (traActualMoney.compareTo(refundMoney) < 0) {
			throw new ServiceException("退款金额不正确");
		}

/*		updateOrder.setStatus(GoodsOrder.ORDER_STATUS_REFUNDING);
		updateOrder.setOrderDes("退款中");

		Integer integer = goodsOrderMapper.updateById(updateOrder);
		if(integer!=1){
			throw new ServiceException("修改退款订单失败");
		}*/

		return TableResult.Result(b);
	}

	/**
	 * 商家同意退款
	 * @param goodsRefundOrder
	 * @return
	 */
	@Override
	public VcQfPayRes agreeGoodsRefundOrder(GoodsRefundOrder goodsRefundOrder) {

		GoodsRefundOrder refundOrder = baseMapper.selectById(goodsRefundOrder.getId());
		if(refundOrder == null){
			throw ServiceException.Exception("退款订单不存在");
		}

		GoodsRefundOrder update = new GoodsRefundOrder();
		update.setId(refundOrder.getId());
		update.setOrderDes("正在退款");
		update.preUpdate();
		update.setStatus(2);
		boolean b = this.updateById(update);

		Map<String, String> requestMap = new HashMap<>();
		requestMap.put("money", refundOrder.getRefundMoney().toString());
		requestMap.put("orderNo", refundOrder.getRefundOrder());
		requestMap.put("merchId", abstractQfWxPayAuth.getMerchId());

		VcQfPayRes vcQfPayRes = qianFangRefundApi.doRefund(requestMap);
		if(vcQfPayRes.isOK()){
			/**
			 * 发送退款成功通知
			 */
			String openId = userService.getOpenIdByUserId(goodsRefundOrder.getUserId());
			ThreadManager.getInstance().execute(
					()->sendMinAppDeliveryMessage(refundOrder, openId, null)
			);
		}
		return vcQfPayRes;
	}
	@Override
	public TableResult sendRefundOrderMessage(Integer id){
		GoodsRefundOrder refundOrder = baseMapper.selectById(id);
		/**
		 * 发送退款拒绝通知
		 */
		String openId = userService.getOpenIdByUserId(id);
		JSONObject jsonObject = sendMinAppDeliveryMessage(refundOrder, openId, null);

		return TableResult.OKResult(jsonObject);
	}
	/**
	 * 买家取消拼团退款
	 * @param goodsRefundOrder
	 * @return
	 */
	@Override
	public VcQfPayRes doCancelCollageRefund(GoodsRefundOrder goodsRefundOrder){

		TableResult result =  refundGoodsOrder(goodsRefundOrder);
		if (!result.OK()){
			throw new ServiceException("发起订单退款失败");
		}

		Map<String, String> requestMap = new HashMap<>();
		requestMap.put("money", goodsRefundOrder.getRefundMoney().toString());
		requestMap.put("orderNo", goodsRefundOrder.getRefundOrder());
		requestMap.put("merchId", abstractQfWxPayAuth.getMerchId());

		VcQfPayRes vcQfPayRes = qianFangRefundApi.doRefund(requestMap);
		return vcQfPayRes;
	}
	/**
	 * 用户退款订单列表
	 * @param page
	 * @param goodsRefundOrder
	 * @return
	 */
	@Override
	public Page<GoodsRefundOrder> selectRefundOrderList(Page<GoodsRefundOrder> page, GoodsRefundOrder goodsRefundOrder) {
		page = baseMapper.selectRefundOrderList(page, goodsRefundOrder);
		//订单类型(1,普通,2,拼团,3,砍价,4套餐)
		List<GoodsRefundOrder> records = page.getRecords();
		for (GoodsRefundOrder refundOrder : records) {
			List<GoodsOrderItem> goodsOrderItems = null;
//				if(refundOrder.getOrderType() == 1){
			GoodsOrderItem query = new GoodsOrderItem();
			query.setRefundOrderId(refundOrder.getId());

			goodsOrderItems = goodsOrderItemMapper.selectOrderItemList(query);

			//活动的退款订单
//				}else {
//					String orderNo = refundOrder.getOrderNo();
//					GoodsOrder orderEnty = new GoodsOrder();
//					orderEnty.setOrderNo(orderNo);
//
//					GoodsOrder goodsOrder = goodsOrderMapper.selectOne(orderEnty);
//					Integer collageOrderId = goodsOrder.getCollageOrderId();
//
//
//					goodsOrderItems = new ArrayList<>();
//					GoodsOrderItem item = new GoodsOrderItem();
//					item.set
////					goodsOrderMapper.select
//				}
			refundOrder.setOrderItems(goodsOrderItems);
		}
		return page;
	}

	public static String[] statusArr = new String[] {"待审核","审核通过","审核拒绝","申请成功","已完成","失败"};
	/**
	 * 发送退货审核通知
	 * vzqvGS50BDWBnyq22L5u71G1zwtIQ7fuWlrn6M-6hJE
	 */
	@Override
	public JSONObject sendMinAppDeliveryMessage(GoodsRefundOrder order, String openId, String form_id) {
		JSONObject result;
		if (form_id == null) {
			Queue<String> formIdList = (Queue<String>) CacheUtils.get(order.getSysUserId() + "");
			if (formIdList == null || formIdList.isEmpty()) {
				result = new JSONObject();
				result.put("code", "0");
				logger.info("推送小程序模板消息失败:没有form_id");
				return result;
			}
			form_id = formIdList.poll();
		}
		logger.info("开始推送小程序模板消息推送:******退货审核通知******");

		List<GoodsOrderItem> orderItems = order.getOrderItems();
		String goodsName = orderItems.get(0).getGoodsName();
		String refundMoney = order.getRefundMoney().toString();
		//审核原因
		String rejectReason = order.getRejectReason();
		String auditTime = DateUtils.formatDate(order.getAuditTime(),"yyyy年MM月dd日 HH:mm:ss");
		String refundNo = order.getRefundOrder();
		String orderNo = order.getOrderNo();
		String remarks = order.getRemarks();
		String status = statusArr[order.getStatus()];

		String[] dataParam = new String[]{
				goodsName,refundMoney, rejectReason,auditTime,refundNo, orderNo,remarks,status
		};
		JSONObject data = WechatUtils.buildMinAppRequestData(openId,
				"vzqvGS50BDWBnyq22L5u71G1zwtIQ7fuWlrn6M-6hJE",
				"",
				form_id,
				0,
				dataParam);
		logger.info("openId==========={}\ntemplat_idopenId==========={}\n", openId, "vzqvGS50BDWBnyq22L5u71G1zwtIQ7fuWlrn6M-6hJE");
		result = WechatUtils.sendWechatmsgToUser(data);
		logger.info(result.toJSONString());
		return result;
	}
}
